package com.example.chat.repository

import com.example.chat.dao.TopicDao
import com.example.chat.dao.TopicParticipantDao
import com.example.chat.model.TopicParticipant
import com.example.chat.model.Topic
import com.example.chat.service.TopicService
import com.example.featuresdk.model.User
import com.example.featuresdk.repository.IRepository
import com.example.featuresdk.repository.ReadAsFlow
import kotlinx.coroutines.flow.Flow
import java.sql.Timestamp
import javax.inject.Inject
import javax.inject.Singleton

@Singleton
class TopicRepository
@Inject constructor(private val topicDao: TopicDao,
                    private val topicParticipantDao: TopicParticipantDao,
                    private val topicService: TopicService
) : IRepository<Topic> {

    override suspend fun get(vararg params: Any): Flow<List<Topic>> {

        val userId = params[0] as Long

        return ReadAsFlow(
            fetchLocalData = { topicDao.getAll() },
            shouldFetchRemoteData = {false},
            fetchRemoteData = { topicService.getTopics(userId) },
            saveRemoteData = { topics -> topicDao.insert(topics)}
        ).execute()
    }

    override suspend fun getOne(vararg params: Any): Flow<Topic> {
        val topicId = params[0] as Long
        return topicDao.getOne(topicId)
    }

    override suspend fun create(items: List<Topic>) {
        topicDao.insert(items)
    }

    override suspend fun create(item: Topic) {
        topicDao.insert(item)
    }

    override suspend fun create(vararg items: Topic) {
        topicDao.insert(*items)
    }

    suspend fun updateSummary(topicId: Long, message: String,timestamp: Timestamp){
        topicDao.update(topicId,message,timestamp)
    }

    suspend fun updateNewCount(topicId: Long){
        topicDao.updateNewCount(topicId)
    }

    suspend fun resetCount(topicId: Long, count:Int = 0){
        topicDao.updateCount(topicId, count)
    }

    fun getAllParticipants(): Flow<Map<Long, List<User>>>{
        return topicParticipantDao.getAll()
    }

    suspend fun getParticipants(topicId: Long):List<User>{
        return topicParticipantDao.getOne(topicId)
    }

    suspend fun createParticipant(userId: Long, topicId: Long){
        topicParticipantDao.insert(TopicParticipant(userId, topicId))
    }
}